import 'reflect-metadata'

/**
 * 添加元数据 值是拦截器组成的数组
 * @param interceptors 拦截器组成的数组
 */
export function UseInterceptors(...interceptors) {
  /**
   * 如果是类装饰器则只有1个参数: 类本身
   * 如果是方法装饰器则拥有3个参数: 类的原型对象 被装饰的方法名 属性描述符
   */
  return (target: object | Function, property?: string, descriptor?: PropertyDescriptor) => {
    
    if (descriptor) { // 方法装饰器
      // 获取方法中 interceptors 元数据 ( 处理一个路由处理函数上多次调用 UseInterceptors 情况 )
      const existingInterceptors = Reflect.getMetadata('interceptors', descriptor.value) ?? []
      // 给方法添加一个 interceptors 元数据 值是拦截器组成的数组 ( 已经保存的拦截器 与当前拦截器合并 )
      Reflect.defineMetadata('interceptors', [...existingInterceptors, ...interceptors], descriptor.value)
    } else { // 类装饰器
      // 获取类中 interceptors 元数据 ( 处理一个控制器类上多次调用 UseInterceptors 情况 )
      const existingInterceptors = Reflect.getMetadata('interceptors', target) ?? []
      // 给类添加一个 interceptors 元数据 值是拦截器组成的数组 ( 已经保存的拦截器与当前拦截器合并 )
      Reflect.defineMetadata('interceptors', [...existingInterceptors, ...interceptors], target)
    }
  }
}
